package com.itlong.cloud.controller.whitelist;

import com.itlong.cloud.POJO.DTO.operate.OperateDeviceAuthFileDTO;
import com.itlong.cloud.POJO.VO.MessageVO;
import com.itlong.cloud.POJO.VO.operate.DeviceAuthFileVO;
import com.itlong.cloud.PlatformConstants;
import com.itlong.cloud.abstracts.BaseController;
import com.itlong.cloud.annotation.AuthAccessRequired;
import com.itlong.cloud.annotation.LoggerInfo;
import com.itlong.cloud.constants.LogDescConstant;
import com.itlong.cloud.enumerate.FileCatalogEnum;
import com.itlong.cloud.enumerate.ecode.BaseErrorCodeEnum;
import com.itlong.cloud.enumerate.ecode.OperateErrorCodeEnum;
import com.itlong.cloud.equip.operate.IOperateDeviceWhiteListAuthFileServiceClient;
import com.itlong.cloud.thrown.DataAccessException;
import com.itlong.cloud.utils.file.UploadFileUtil;
import com.itlong.cloud.utils.network.http.HttpProtocolUtil;
import com.itlong.cloud.utils.page.Page;
import com.itlong.cloud.utils.words.StringHandlerUtil;
import org.apache.commons.fileupload.servlet.ServletFileUpload;
import org.apache.commons.lang.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.web.multipart.MultipartHttpServletRequest;

import javax.servlet.http.HttpServletRequest;
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * <desc>
 *      运营-设备白名单授权文件控制器
 * </desc>
 *
 * @createDate2020/8/13
 **/
@RestController
@RequestMapping("whiteList/authFile")
public class OperateWhiteListAuthFilesController extends BaseController {

    @Autowired
    private IOperateDeviceWhiteListAuthFileServiceClient iOperateDeviceWhiteListAuthFileServiceClient;

    @Value("${" + PlatformConstants.FILE_FTP_HOST + "}")
    public String FILE_FTP_HOST;

    @Value("${" + PlatformConstants.FILE_FTP_PORT + "}")
    public String FILE_FTP_PORT;

    @Value("${" + PlatformConstants.FILE_FTP_USERNAME + "}")
    public String FILE_FTP_USERNAME;

    @Value("${" + PlatformConstants.FILE_FTP_PASSWORD + "}")
    public String FILE_FTP_PASSWORD;

    @Value("${" + PlatformConstants.FILE_ACCESS_URL + "}")
    public String FILE_ACCESS_URL;
    /**
     * <desc>
     *      分页获取授权文件列表
     * </desc>
     *
     * @param operateDeviceAuthFileDTO 授权文件查询参数
     * @return 格式化响应结果
     * @Author Zhu.yj
     * @createDate  2020/8/14
     */
    @RequestMapping(value = "getPage", method = RequestMethod.POST)
    public Object getPage(OperateDeviceAuthFileDTO operateDeviceAuthFileDTO, HttpServletRequest request){
        try {
            operateDeviceAuthFileDTO = HttpProtocolUtil.parseRequestParamToDTO(OperateDeviceAuthFileDTO.class, request);
            String myUserName = request.getAttribute("myUserName") == null ? null : request.getAttribute("myUserName").toString();
            operateDeviceAuthFileDTO.setLoginUserId(myUserName);
            Page<DeviceAuthFileVO> page = iOperateDeviceWhiteListAuthFileServiceClient.getPage(operateDeviceAuthFileDTO);
            return new MessageVO(BaseErrorCodeEnum.SUCCESS.getErrorCode(), page);
        }catch (Exception e){
            throw new DataAccessException("【运营_设备白名单授权文件管理getPage】分页获取授权文件列表失败" ,e);
        }
    }

    /**
     * <desc>
     *      添加授权文件
     * </desc>
     *
     * @Author Zhu.yj
     * @createDate  2020/8/14
     */
    @AuthAccessRequired
    @LoggerInfo(operateDesc = LogDescConstant.OPERATE_DEVICE_WHITE_LIST_AUTH_FILE_ADD_LOG_DESC)
    @RequestMapping(value = "save", method = RequestMethod.POST)
    public Object save(OperateDeviceAuthFileDTO operateDeviceAuthFileDTO, HttpServletRequest request, String myUserName){
        try {
            operateDeviceAuthFileDTO = HttpProtocolUtil.parseRequestParamToDTO(OperateDeviceAuthFileDTO.class, request);
            if (operateDeviceAuthFileDTO == null || StringUtils.isBlank(operateDeviceAuthFileDTO.getEffectiveTimes())){
                return new MessageVO(BaseErrorCodeEnum.NOT_PARAM.getErrorCode());
            }
            myUserName = request.getAttribute("myUserName") == null ? null : request.getAttribute("myUserName").toString();
            boolean isMultipart = ServletFileUpload.isMultipartContent(request);
            if (!isMultipart){
                return new MessageVO(OperateErrorCodeEnum.PROJECT_IMPORT_FILE_LOST_ERR.getErrorCode());
            }
            MultipartHttpServletRequest multipartRequest = (MultipartHttpServletRequest) request;
            Map<String, MultipartFile> multipartFileMap = multipartRequest.getFileMap();
            if (multipartFileMap.size() < 1){
                return new MessageVO(OperateErrorCodeEnum.PROJECT_IMPORT_FILE_LOST_ERR.getErrorCode());
            }
            //授权文件
            MultipartFile authFile = multipartRequest.getFile("authFile");
            if (authFile == null){
                return new MessageVO(OperateErrorCodeEnum.DEVICE_WHITE_LIST_AUTH_FILE_LOSE_ERR.getErrorCode());
            }
            String fileName = authFile.getOriginalFilename();
            if (iOperateDeviceWhiteListAuthFileServiceClient.getCountByFileName(fileName) > 0){
                return new MessageVO(OperateErrorCodeEnum.DEVICE_WHITE_LIST_FILE_NAME_REPEAT_ERR.getErrorCode());
            }
            operateDeviceAuthFileDTO.setFileName(fileName);
            String fileType = StringHandlerUtil.copySubStr(fileName, fileName.lastIndexOf('.') + 1, fileName.length());
            long fileSize = authFile.getSize();
            //授权文件只能删除zip格式的
            if (!"zip".equals(fileType)){
                return new MessageVO(OperateErrorCodeEnum.DEVICE_WHITE_LIST_AUTH_FILE_TYPE_ERR.getErrorCode());
            }
            //次数凭证文件大小限制500kb
            if (fileSize > 500000){
                return new MessageVO(OperateErrorCodeEnum.DEVICE_WHITE_LIST_AUTH_FILE_TOO_LARGE_ERR.getErrorCode());
            }
            operateDeviceAuthFileDTO.setFileSize(fileSize);
            //先上传授权文件
            InputStream fileStream = authFile.getInputStream();
            String authFileUrl = this.uploadFile(fileStream, fileName, FileCatalogEnum.DEVICE_WHITE_LIST_AUTH_FILE_FILE.getType());
            operateDeviceAuthFileDTO.setAuthFileUrl(authFileUrl);
            //获取次数凭证文件的文件地址
            StringBuilder evidenceUrl = new StringBuilder();
//            List<MultipartFile> evidenceFileList = multipartRequest.getFiles("evidenceFiles");
//            if (evidenceFileList.size() > 3){
//                return new MessageVO(OperateErrorCodeEnum.DEVICE_WHITE_LIST_EVIDENCE_FILE_TOO_MANY_ERR.getErrorCode());
//            }
            //上传次数凭证文件
//            if (!evidenceFileList.isEmpty()){
//                for (MultipartFile multipartFile : evidenceFileList){
//                    InputStream evidenceFileStream = multipartFile.getInputStream();
//                    String evidenceFileName = multipartFile.getOriginalFilename();
//                    String evidenceFileUrl = this.uploadFile(evidenceFileStream, evidenceFileName, FileCatalogEnum.DEVICE_WHITE_LIST_TIMES_EVIDENCE_FILE.getType());
//                    if (evidenceUrl.length() == 0){
//                        evidenceUrl.append(evidenceFileUrl);
//                    }else {
//                        evidenceUrl.append(",");
//                        evidenceUrl.append(evidenceFileUrl);
//                    }
//                }
//
//            }
            //次数凭证文件,由于前端无法一次传递多个文件，所以次数凭证文件一个一个传递临时更名为 evidenceFiles1,evidenceFiles2,evidenceFiles3
            MultipartFile evidenceFiles1 = multipartRequest.getFile("evidenceFiles1");
            MultipartFile evidenceFiles2 = multipartRequest.getFile("evidenceFiles2");
            MultipartFile evidenceFiles3 = multipartRequest.getFile("evidenceFiles3");
            List<Map<String, Object>> list = new ArrayList<>();
            if (evidenceFiles1 != null){
                this.getEvidenceUrl(evidenceFiles1, list);
            }
            if (evidenceFiles2 != null){
                this.getEvidenceUrl(evidenceFiles2, list);
            }
            if (evidenceFiles3 != null){
                this.getEvidenceUrl(evidenceFiles3, list);
            }
            operateDeviceAuthFileDTO.setEvidenceFileUrlList(list);
            operateDeviceAuthFileDTO.setLoginUserId(myUserName);
            //添加操作
            iOperateDeviceWhiteListAuthFileServiceClient.save(operateDeviceAuthFileDTO);
            return new MessageVO(BaseErrorCodeEnum.SUCCESS.getErrorCode());
        }catch (Exception e){
            throw new DataAccessException("【运营_设备白名单授权文件管理save】添加授权文件失败", e);
        }
    }

    /**
     * <desc>
     *      删除授权文件
     * </desc>
     *
     * @Author Zhu.yj
     * @createDate  2020/8/14
     */
    @AuthAccessRequired
    @LoggerInfo(operateDesc = LogDescConstant.OPERATE_DEVICE_WHITE_LIST_AUTH_FILE_DELETE_LOG_DESC)
    @RequestMapping(value = "delete", method = RequestMethod.POST)
    public Object delete(OperateDeviceAuthFileDTO operateDeviceAuthFileDTO, HttpServletRequest request){
        try {
            operateDeviceAuthFileDTO = HttpProtocolUtil.parseRequestParamToDTO(OperateDeviceAuthFileDTO.class, request);
            if (operateDeviceAuthFileDTO == null || StringUtils.isBlank(operateDeviceAuthFileDTO.getAuthId())){
                return new MessageVO(BaseErrorCodeEnum.NOT_PARAM.getErrorCode());
            }
            iOperateDeviceWhiteListAuthFileServiceClient.delete(operateDeviceAuthFileDTO);
            return new MessageVO(BaseErrorCodeEnum.SUCCESS.getErrorCode());
        }catch (Exception e){
            throw new DataAccessException("【运营_设备白名单授权文件管理delete】删除授权文件失败", e);
        }
    }

    /**
     * <desc>
     *      获取次数凭证地址url
     * </desc>
     *
     * @param authId 授权文件id
     * @return
     * @Author Zhu.yj
     * @createDate  2020/8/16
     */
    @RequestMapping(value = "getTimesEvidence", method = RequestMethod.POST)
    public Object getTimesEvidence(String authId, HttpServletRequest request) {
        try {
            authId = request.getAttribute("authId") == null ? null : request.getAttribute("authId").toString();
            if (StringUtils.isBlank(authId)){
                return new MessageVO(BaseErrorCodeEnum.NOT_PARAM.getErrorCode());
            }
            List<Map<String, Object>> evidenceFileUrl = iOperateDeviceWhiteListAuthFileServiceClient.getTimesEvidence(authId);
            return new MessageVO(BaseErrorCodeEnum.SUCCESS.getErrorCode(), evidenceFileUrl);
        }catch (Exception e){
            throw new DataAccessException("【运营_设备白名单授权文件管理getTimesEvidence】获取授权文件信息失败", e);
        }
    }

    /**
     * <desc>
     *      Ftp上传文件，返回Url.
     * </desc>
     *
     * @param inputStream 文件流
     * @param fileName 文件名称
     * @return 文件上传成功后会返回Url,否则返回空
     * @author wangzhi
     * @createDate 2018/06/28
     */
    private String uploadFile(InputStream inputStream, String fileName, String fileCatalogName) throws IOException {
        String fileUrl = "";
        String fileType = StringHandlerUtil.copySubStr(fileName,fileName.lastIndexOf('.')+1,fileName.length());
        UploadFileUtil.UploadFile uploadFileUtil = new UploadFileUtil().new UploadFile(
                FILE_FTP_HOST,
                FILE_FTP_USERNAME,
                FILE_FTP_PASSWORD,
                FILE_FTP_PORT,
                inputStream,
                fileType,
                FILE_ACCESS_URL,
                fileCatalogName
        );
        Map<String, Object> resultMap = UploadFileUtil.uploadFile(uploadFileUtil);
        Boolean returnCode = (Boolean)resultMap.get("returnCode");
        if (!returnCode){
            return fileUrl;
        }
        fileUrl = resultMap.get("accessPath").toString();
        return fileUrl;
    }

    /**
     * <desc>
     *      获取次数凭证文件地址
     * </desc>
     *
     * @param file file文件
     * @param list 待保存次数平整文件列表
     * @return
     * @Author Zhu.yj
     * @createDate  2020/8/17
     */
    private void getEvidenceUrl(MultipartFile file, List<Map<String, Object>> list) throws Exception{
        Map<String, Object> params = new HashMap<>();
        InputStream inputStream = file.getInputStream();
        String originalFilename = file.getOriginalFilename();
        String fileUrl = this.uploadFile(inputStream, originalFilename, FileCatalogEnum.DEVICE_WHITE_LIST_TIMES_EVIDENCE_FILE.getType());
        params.put("fileName", originalFilename);
        params.put("fileUrl", fileUrl);
        list.add(params);
    }


}
